import urllib3
import lxml.html
from selenium import webdriver
from time import sleep
import pymongo

import lianjia


class DealRecord(lianjia.Base):

    # def __init__(self, proxy, city, username, password, callback=None):
    #     lianjia.Base.__init__(self, proxy, city, callback)
    #     driver = webdriver.Chrome()
    #     driver.get(self._url_formatter % (self._city, ''))
    #     driver.implicitly_wait(30)
    #     login_button = driver.find_element_by_css_selector('a.btn-login.bounceIn.actLoginBtn')
    #     # actions = webdriver.ActionChains(driver)
    #     # actions.move_to_element_with_offset(login_button, 100, 0).click().perform()
    #     driver.execute_script('arguments[0].click()', login_button)
    #     sleep(1)
    #     login_by_account_button = driver.find_element_by_css_selector('#con_login_user_tel > form > ul > li.footer-link > a')
    #     login_by_account_button.click()
    #     sleep(1)
    #     username_input = driver.find_element_by_css_selector('input.the_input.topSpecial.users')
    #     username_input.send_keys(username)
    #     password_input = driver.find_element_by_css_selector('input.the_input.password')
    #     password_input.send_keys(password)
    #     sign_in_button = driver.find_element_by_css_selector('a.login-user-btn')
    #     sign_in_button.click()
    #     sleep(5)
    #     self.session_cookie = driver.get_cookie('TY_SESSION_ID')
    #     driver.close()

    def _load_apartment(self, url):
        response: urllib3.HTTPResponse = self._http.request('GET', url)
        if response.status != 200:
            return None

        document: lxml.html.HtmlElement = lxml.html.fromstring(response.data)
        apartment = {}

        sold_date = document.cssselect('body > div.house-title > div > span')  # type: list[lxml.html.HtmlElement]
        if len(sold_date) == 1:
            apartment['soldDate'] = ''.join(filter(lambda ch: ch in '0123456789.', sold_date[0].text))

        desired_price = document.cssselect('div.overview > div.info.fr > div.msg > span:nth-child(1) > label')  # type: list[lxml.html.HtmlElement]
        if len(desired_price) == 1:
            apartment['desiredPrice'] = float(desired_price[0].text)

        price = document.cssselect('div.price > span.dealTotalPrice > i')  # type: list[lxml.html.HtmlElement]
        if len(price) == 1:
            apartment['price'] = float(price[0].text)

        index = url.rfind('/')
        if index >= 0:
            code = url[index + 1:]
        index = code.rfind('.')
        if index >= 0:
            code = code[:index]
        apartment['_id'] = code

        return apartment

    def _load_apartments(self, page):
        apartments = []
        response: urllib3.HTTPResponse = self._http.request('GET', self._url_formatter % (self._city, '/chengjiao/pg' + page + '/'))
        if response.status != 200:
            return []

        document: lxml.html.HtmlElement = lxml.html.fromstring(response.data)
        elements = document.cssselect('ul.listContent > li')  # type: list[lxml.html.HtmlElement]
        for element in elements:

            elements_title = element.cssselect('div.title > a')  # type: list[lxml.html.HtmlElement]
            if len(elements_title) == 1:
                elements_title_first = elements_title[0]
                code = elements_title_first.attrib['href']  # type: str
                apartment = self._load_apartment(code)
                if apartment:
                    apartments.append(apartment)

        return apartments

    def run(self):
        client = pymongo.MongoClient(host='localhost', port=27017)
        db = client.lianjia
        collection: pymongo.collection.Collection = db.products

        date = None
        for i in range(1, 101):
            apartments = self._load_apartments(str(i))
            if len(apartments) == 0:
                break
            if not date:
                date = apartments[0]['soldDate']

            apartments_of_last_day = [apartment for apartment in apartments if apartment['soldDate'] == date]
            apartments_to_insert = []
            for apartment in apartments_of_last_day:
                new = apartment.copy()
                new.pop('_id')
                if not collection.find_one_and_update({'_id': apartment['_id']}, {'$set': new}):
                    apartments_to_insert.append(apartment)
            if len(apartments_to_insert) > 0:
                collection.insert_many(apartments_to_insert)

            if self._callback:
                if not self._callback(apartments):
                    return
            else:
                pass

            if len(apartments_of_last_day) < len(apartments):
                return
